package collections.list;


import java.util.Iterator;

public class ListImpl<T> implements SingleLinkedList<T> {
    private int size;
    private ListElement head;
    private ListElement tail;

    @Override
    public void add(T value) {
        ListElement elem = new ListElement(value);

        if (head == null) {
            head = tail = elem;

        } else {
            tail.setNode(elem);
            tail = elem;
        }
        size++;
    }

    @Override
    public boolean remove(T value) {
        if (head == null) return false;

        if (head.equals(value)){
            if (head.getNode() == null) {
                head = null;
            } else {
                head = head.getNode();
            }
            size--;
            return true;
        }

        for (ListElement tmp = head; tmp.getNode() != null; tmp = tmp.getNode()) {
            ListElement check = tmp.getNode();
            if (check.equals(value)){
                tmp.setNode(check.getNode());
                size--;
                return true;
            }
        }
        return false;
    }

    @Override
    public void removeAll() {
        head = tail = null;
        size = 0;
    }

    @Override
    public boolean contains(T value) {
        ListElement tmp = head;

        while (tmp != null) {
            if(tmp.equals(value)) return true;
            tmp = tmp.getNode();
        }

        return false;
    }

    @Override
    public int size() {
        return size;
    }

    @Override
    public Iterator iterator() {
        return new Iterator() {
            private int index = 0;
            private ListElement tmp = head;

            @Override
            public boolean hasNext() {
                if (tmp == null) return false;
                return tmp.getNode()!= null;
            }

            @Override
            public Object next() {
                tmp = (index == 0) ? tmp : tmp.getNode();
                index++;
                return tmp.getValue();
            }

            @Override
            public void remove() {

            }
        };
    }
}
